﻿using FlyRemote.Base;
using System;

namespace FlyRemote.Remote
{
    /// <summary>
    /// 数据收集，比较，存放结果的最小单位， 对应一个当前的扫描类型
    /// 结构大小 是  32
    /// !!! 注意 Cell 并不是 严格的值类型(里面有一个对象)，所以 无法声明它的引用 
    /// </summary>
    public readonly struct SnapshotCell
    {
        #region 数据 

        public readonly ReadGroup ReadGroup;

        /// <summary>
        /// 相对于读取组的偏移
        /// </summary>
        public readonly int ReadGroupOffset;

        /// <summary>
        /// 区间大小 
        /// </summary>
        public readonly int RegionSize;


        #endregion


        /// <summary>
        /// 快照区间 是 位于一个读取组内部  
        /// </summary>
        /// <param name="readGroup">The read group of this snapshot region.</param>
        /// <param name="baseAddress">The base address of this snapshot region.</param>
        /// <param name="regionSize">The size of this snapshot region.</param>
        public SnapshotCell(ReadGroup readGroup, int readGroupOffset, int regionSize)
        {
            this.ReadGroup = readGroup;
            this.ReadGroupOffset = readGroupOffset;
            this.RegionSize = regionSize;

        }

        public SnapshotCell(ulong baseAddress, ReadGroup readGroup, int regionSize)
        {
            this.ReadGroup = readGroup;
            this.ReadGroupOffset = (int)(baseAddress - readGroup.BaseAddress);
            this.RegionSize = regionSize;

        }


        public override string ToString()
        {
            return $"{BaseAddress.ToString("X")} {RegionSize}";
        }



        /// <summary>
        /// Gets the base address of the region.
        /// </summary>
        public UInt64 BaseAddress
        {
            get
            {
                return this.ReadGroup.BaseAddress.Add(this.ReadGroupOffset);
            }
        }

        /// <summary>
        /// 结束地址
        /// </summary>
        public UInt64 EndAddress
        {
            get
            {
                return this.ReadGroup.BaseAddress.Add(this.ReadGroupOffset + this.RegionSize);
            }
        }

        public bool IsInModule { get => ReadGroup.IsModuleRegion; }


        /// <summary>
        /// 是否具有当前值
        /// </summary>
        //public unsafe Boolean HasCurrentValue()
        //{
        //    return (!this.ReadGroup.CurrentValues.IsNullOrEmpty());
        //}

        ///// <summary>
        ///// 是否有先前值
        ///// </summary>
        //public unsafe Boolean HasPreviousValue()
        //{
        //    return (!this.ReadGroup.PreviousValues.IsNullOrEmpty());

        //}
        //public Object LoadCurrentValue(DataType type = null)
        //{
        //    if (type == null)
        //        return ReadGroup.ElementDataType.FromBytes(ReadGroup.CurrentValues, this.ReadGroupOffset);
        //    else
        //        return type.FromBytes(ReadGroup.CurrentValues, this.ReadGroupOffset);
        //}

        //public Object LoadPreviousValue(DataType type = null)
        //{
        //    if (type == null)
        //        return ReadGroup.ElementDataType.FromBytes(ReadGroup.PreviousValues, this.ReadGroupOffset);
        //    else
        //        return type.FromBytes(ReadGroup.PreviousValues, this.ReadGroupOffset);
        //}
    }

}
